#ifndef GENERAL_H_INCLUDED
#define GENERAL_H_INCLUDED
#include <cstdlib>
#include <string>
#include <time.h>
#include <ctime>
#include <sstream>
#include <iostream>
#include <fstream>
#include <cmath>
#include <vector>
#include <SFML/Graphics.hpp>
#define BS_DEPLACEMENT 1
#define BS_VIE 2
#define BS_VIEMAX 3
#define BS_PUISSANCE 4
#define BS_PUISSANCEMAX 5
#include "..\Unite\unite.h"
#include "..\GamePlay\map.h"
#include "..\System\collision.h"
#include "..\Interface\interface.h"
#include "..\System\Option.h"
extern int XPLACEMENT_BATIMENT;
class Vue
{
    public:
    Vue(sf::Vector2f centre, sf::Vector2f demitaille);
    ~Vue();
    void deplacer(int valeur, Terrain *terre);
    void setPosition(int x, Terrain *terre);
    sf::View getvue();

    private:
    sf::View *m_vue;
    sf::Vector2f m_centre, demitaille;

};
class Batiment
{
    public:
    Batiment(std::string image, int vie, int type);
    ~Batiment();
    void ChargerCaractere(std::string fichier);
    bool IsCollideUnite(sf::Sprite unite);
    bool Placeable(float x, Terrain *terre, int xmax, int xmin);
    void Placer(float x, float y, bool placer);
    void SetPlaceable(bool placeable);
    void Afficher(sf::RenderWindow *app, bool visible);
    sf::Vector2f GetPosition();
    int GetVie();
    int GetType();
    void Degat(float degat);
    sf::Sprite GetSprite();
    void AjouterUnite(Unite* uniter, int id);
    void RemoveUnite(Unite* uniter, int id);

    private:
    std::vector<int> unite_in_place;
    std::vector<sf::Sprite> sprite_unite;
    std::vector<sf::Vector2f> position_unite;
    int m_vie, m_viemax, m_type, m_nombre_unite;
    bool en_creation, m_placer, m_placeable;
    int m_t,curseur;
    std::string fichier_image;
    sf::Vector2f m_position;
    sf::Texture image_batiment, image_batimenton, image_batimentoff, m_imagevie;
    sf::Sprite sprite_batiment;
    sf::Sprite sprite_batimenton, sprite_batimentoff, m_spritevie;
};
class Equipe
{
    public:
    Equipe();
    ~Equipe();
    void AddUniteId(int id, std::vector<Unite*> m_unite);
    void SetIa(bool ia);
    void Rafraichir(std::vector<Unite*> m_unite);
    void RafraichirEffect(std::vector<Unite*> m_unite, Terrain *terre);
    int GetUniteActuel();
    int GetUniteTotal();
    int GetPoint();
    int GetUnite(int id);
    void Achat(int prix);
    void Suivant();
    void Precedent();
    bool GetAlive();
    bool IsExplosion(int type);
    bool GetIa();
    float GetPourcentVie();
    void GetXmaxmin(int *max, int *min);
    void SetBasePosition(float x, Terrain *terre);
    void Afficher(sf::RenderWindow *app, int id, bool visible);
    Batiment GetBatiment(int id);
    int GetNumberBatiment();
    void AddBatiment(std::vector<Unite*> m_unite);
    void CreateBatiment(int type, int sous_type, sf::Vector2f position, Terrain *terre);
    bool CanPlaceBatiment(sf::Vector2f position, Terrain *terre);
    void PlacerBatiment(int id, bool placeable, bool placer, sf::Vector2f position);

    private:
    std::vector<int> unite_id;
    std::vector<Batiment*> m_batiment;
    int unite_actuel;
    int vie_total;
    int vie;
    int point;
    int m_prix;
    int m_tmp_type, m_tmp_sous_type;
    int xmin, xmax;
    sf::Vector2f m_tmp_position;
    bool is_Ia, is_Alive, In_to_Create_Batiment, Explosion_resistance, Explosion_damage;
};
class Game
{
    public:
    Game(std::string fichier);
    ~Game();
    void setFichier(std::string fichier);
    void addUnite(Unite *unite);
    void boucle(sf::RenderWindow *app, int ia);
    void degat(int explosion, sf::Vector2f position, int degat, bool balle, int id_balle, bool to_infant);
    void rafraichir_position();
    void rafraichir_equip();
    void gagner();
    void pause(sf::RenderWindow *app,sf::Vector2f souris, bool Clique, bool Even, int type);
    void finTire();
    void AjouterBatiment(int equipe, int type, int sous_type, sf::Vector2f position);
    std::vector<Unite*> GetUnite();
    Terrain *m_terre;

    private:
    std::vector<Unite*> m_unite;
    std::vector<sf::Sprite> m_spriteunite;
   // RoquetteMulti triboulet;
    sf::Clock clock;
    float m_time;
    Vue *fenetre;
    int nombre_joueur, tour, equipe_actu, equipe_gagnante, typePause, curseur_interface;
    Equipe equipe_id[4];
    bool vue_suivit, enPause;
    sf::Font font;
    sf::Text rate;
    std::vector<Batiment> m_batiment_neutre;
    // Gui equipe
    sf::Texture image_equipe;
    sf::Sprite sprite_fondequipe[4], sprite_devantequipe[4], sprite_vieequipe[4];
    sf::Text texte_equipe[4];
    // Gui interface
    sf::Texture image_fond, image_fond_devant, image_jauge, image_bouton;
    sf::Sprite sprite_fond, sprite_fond_devant, sprite_puissance, sprite_vie_unite, sprite_vie_base, sprite_hopital, sprite_garage, sprite_armurerie, sprite_radar;
    sf::Sprite sprite_pompe, sprite_c4, sprite_soin, sprite_reparation, sprite_invisible;
    sf::Text texte_point, texte_nbbatiment, texte_statut;
    // Menu pause
    sf::Texture image_boutonpause, image_fondpause;
    sf::Sprite sprite_boutonquitter, sprite_boutonreprendre, sprite_boutonretourmenu, sprite_boutonoption;
    sf::Sprite sprite_fondpause;
    // Tableau equipe
    sf::Texture image_tableauequipe;
    sf::Sprite sprite_tableauequipe;
    sf::Text texte_nomequipe, texte_nomunite;
    //Changement equipe
    sf::Texture image_changementequipe;
    sf::Sprite sprite_changementequipe;
    sf::Text texte_changementequipe;
    //Curseur unite
    sf::Texture image_curseur;
    sf::Sprite sprite_curseur;
};
#endif // GENERAL_H_INCLUDED
